﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.ComponentModel;
using System.Globalization;

namespace PGun.MVC.Core.ComponentModel
{
    public class GenericListTypeConverter<T> : TypeConverter
    {
        protected readonly TypeConverter typeConvertor;

        public GenericListTypeConverter()
        {
            typeConvertor = TypeDescriptor.GetConverter(typeof (T));
            if(typeConvertor == null)
                throw  new InvalidOperationException("존재하지 않는 데이터 형식입니다." + typeof(T).FullName);
        }

        protected virtual string[] GetStringArray(string Input)
        {
            if (!string.IsNullOrEmpty(Input))
            {
                string[] result = Input.Split(',');
                Array.ForEach(result, s => s.Trim());
                return result;
            }
            else
            {
                return new string[0];
            }
        }

        public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
        {
            if(sourceType == typeof(string))
            {
                string[] items = GetStringArray(sourceType.ToString());
                return items.Any();
            }

            return base.CanConvertFrom(context, sourceType);
        }

        public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
        {
            if (value is string)
            {
                string[] items = GetStringArray((string)value);
                var result = new List<T>();
                Array.ForEach(items, s =>
                    {
                        object item = typeConvertor.ConvertFromInvariantString(s);
                        if (item != null)
                        {
                            result.Add((T)item);
                        }
                    }
                    );
                return result;
            }
            return base.ConvertFrom(context, culture, value);
        }

        public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
        {
            if (destinationType == typeof (string))
            {
                string result = string.Empty;
                if ((IList<T>) value != null)
                {
                    for (int i = 0; i < ((IList<T>) value).Count; i++)
                    {
                        var str1 = Convert.ToString(((IList<T>) value)[i], CultureInfo.InvariantCulture);
                        result += str1;
                        if (i != ((IList<T>) value).Count - 1)
                            result += ",";
                    }
                }
                return  result;
            
            }
            return base.ConvertTo(context, culture, value, destinationType);
        }


    }
}
